package model {
	import fs.message.MessageTransmitter;
	import message.GameMessage;
	/**
	 * ...
	 * @author flyingSnow
	 */
	public final class GameData {
		private var _players:Array;
		private var _crntPlayerIndex:int;
		private var _crntPieces:BitBoard;
		private var _gameResult:Array;
		
		public function GameData() {
			_players = [ new AiPlayer(this), new AiPlayer(this), new AiPlayer(this), new AiPlayer(this)];
			_crntPlayerIndex = 0;
			_crntPieces = new BitBoard();
		}
		
		public function getPlayer(i:int):Player {
			return _players[i];
		}
		public function get totalPlayers():int {
			return _players.length;
		}
		public function get crntPlayer():Player {
			return _players[_crntPlayerIndex];
		}
		public function canPutPiece(piece:int, direction:int, column:int, row:int):Boolean {
			var testBB:BitBoard = new BitBoard();
			testBB.putPiece(piece, direction, column, row);
			if (testBB.and(_crntPieces).isZero) {
				return true;
			}
			return false;
		}
		
		public function nextPlayer():Boolean {
			var count:int = 0;
			do {				
				if (count==4) {
					gameOver();
					return false;
				}				
				_crntPlayerIndex++;
				_crntPlayerIndex %= _players.length;
				count++;
			}while (!crntPlayer.hasUsabledPiece);
			
			crntPlayer.resetUsableIndex();
			return true;
		}
		
		private function gameOver():void {
			_gameResult = _players.sortOn("score", Array.RETURNINDEXEDARRAY | Array.DESCENDING);
			MessageTransmitter.transmitMessage(GameMessage.GAME_OVER, { res:_gameResult } );
			return;
		}
		
		public function putPiece(piece:int, direction:int, column:int, row:int):void {
			_crntPieces.putPiece(piece, direction, column, row);
		}
		
		public function get clone():GameData {
			var cloneData:GameData = new GameData();
			cloneData._crntPlayerIndex = _crntPlayerIndex;
			cloneData._crntPieces = _crntPieces.clone;
			cloneData._players = [];
			for each(var player:Player in _players) {
				cloneData._players.push(player.getClone(cloneData));
			}
			return cloneData;
		}
		public function get crntPieces():BitBoard { return _crntPieces; }
		
		public function set crntPieces(value:BitBoard):void {
			_crntPieces = value;
		}
		
		public function get crntPlayerIndex():int { return _crntPlayerIndex; }
	}

}